---
sidebar_position: 1
---

# Agents

LangChain offers a number of tools and functions that allow you to create SQL Agents which can provide a more flexible way of interacting with SQL databases. The main advantages of using SQL Agents are:

- It can answer questions based on the databases schema as well as on the databases content (like describing a specific table).
- It can recover from errors by running a generated query, catching the traceback and regenerating it correctly.
- It can query the database as many times as needed to answer the user question.

To initialize the agent we'll use the [`createOpenAIToolsAgent`](https://api.js.langchain.com/functions/langchain_agents.createOpenAIToolsAgent.html) function.
This agent uses the [`SqlToolkit`](https://api.js.langchain.com/classes/langchain_agents_toolkits_sql.SqlToolkit.html) which contains tools to:

- Create and execute queries
- Check query syntax
- Retrieve table descriptions
- … and more

## Setup

First, install the required packages and set your environment variables. This example will use OpenAI as the LLM.

```bash
npm install langchain @langchain/community @langchain/openai typeorm sqlite3
```

```bash
export OPENAI_API_KEY="your api key"
# Uncomment the below to use LangSmith. Not required.
# export LANGCHAIN_API_KEY="your api key"
# export LANGCHAIN_TRACING_V2=true
```

The below example will use a SQLite connection with Chinook database. Follow these [installation steps](https://database.guide/2-sample-databases-sqlite/) to create `Chinook.db` in the same directory as this notebook:

- Save [this](https://raw.githubusercontent.com/lerocha/chinook-database/master/ChinookDatabase/DataSources/Chinook_Sqlite.sql) file as `Chinook_Sqlite.sql`
- Run sqlite3 `Chinook.db`
- Run `.read Chinook_Sqlite.sql`
- Test `SELECT * FROM Artist LIMIT 10;`

Now, `Chinhook.db` is in our directory and we can interface with it using the Typeorm-driven `SqlDatabase` class:

import CodeBlock from "@theme/CodeBlock";
import DbCheck from "@examples/use_cases/sql/db_check.ts";

<CodeBlock language="typescript">{DbCheck}</CodeBlock>

## Initializing the Agent

We'll use an OpenAI chat model and an "openai-tools" agent, which will use OpenAI's function-calling API to drive the agent's tool selection and invocations.

As we can see, the agent will first choose which tables are relevant and then add the schema for those tables and a few sample rows to the prompt.

import AgentExample from "@examples/use_cases/sql/agents/index.ts";

<CodeBlock language="typescript">{AgentExample}</CodeBlock>

:::tip

You can see the LangSmith traces from the example above [here](https://smith.langchain.com/public/8bdedd3f-a76a-4968-878f-ad7366540baa/r) and [here](https://smith.langchain.com/public/6b3f932a-3f37-4946-8db4-99cc826da7de/r)

:::

## Using a dynamic few-shot prompt

To optimize agent performance, we can provide a custom prompt with domain-specific knowledge. In this case we'll create a few shot prompt with an example selector, that will dynamically build the few shot prompt based on the user input. This will help the model make better queries by inserting relevant queries in the prompt that the model can use as reference.

First we need some user input SQL query examples:

import ExampleList from "@examples/use_cases/sql/agents/examples.ts";

<CodeBlock language="typescript">{ExampleList}</CodeBlock>

Now we can create an example selector. This will take the actual user input and select some number of examples to add to our few-shot prompt.
We'll use a SemanticSimilarityExampleSelector, which will perform a semantic search using the embeddings and vector store we configure to find the examples most similar to our input:

import ExampleSelector from "@examples/use_cases/sql/agents/example_selector.ts";

<CodeBlock language="typescript">{ExampleSelector}</CodeBlock>

:::tip

You can see a LangSmith trace of this example [here](https://smith.langchain.com/public/18962b1f-e8d9-4928-9813-49031e421a0a/r)

:::

## Dealing with high-cardinality columns

In order to filter columns that contain proper nouns such as addresses, song names or artists, we first need to double-check the spelling in order to filter the data correctly.

We can achieve this by creating a vector store with all the distinct proper nouns that exist in the database.
We can then have the agent query that vector store each time the user includes a proper noun in their question, to find the correct spelling for that word.
In this way, the agent can make sure it understands which entity the user is referring to before building the target query.

First we need the unique values for each entity we want, for which we define a function that parses the result into a list of elements:

import HighCardinalityExample from "@examples/use_cases/sql/agents/high_cardinality_columns.ts";

<CodeBlock language="typescript">{HighCardinalityExample}</CodeBlock>

:::tip

You can see a LangSmith trace of this example [here](https://smith.langchain.com/public/5b4e6f56-d252-4d3d-af74-638dc0d1d9cb/r)

:::

## Next steps

To learn more about the built-in generic agent types as well as how to build custom agents, head to the [Agents Modules](/docs/modules/agents).

The built-in `AgentExecutor` runs a simple Agent action -> Tool call -> Agent action… loop. To build more complex agent runtimes, head to the [LangGraph section](docs/langgraph).
